import { Provide, Scope, ScopeEnum, Init, Inject, ILogger } from '@midwayjs/core';
import { DataSource, DataSourceOptions } from 'typeorm';
import * as oracledb from 'oracledb';

@Provide()
@Scope(ScopeEnum.Singleton)
export class OracleService {
  @Inject()
  logger: ILogger;

  private oracleDataSource: DataSource | null = null;
  private isInitialized = false;

  @Init()
  async init() {
    if (this.isInitialized) return;

    try {
      const instantClientLibDir = process.env.ORACLE_LIB_DIR || 'C:\\oracle\\instantclient_19_26';
      this.logger.info(`(OracleService) Initializing Oracle Client (Thick mode) using libDir: ${instantClientLibDir}`);
      // Make sure oracledb is available and initOracleClient is a function
      if (typeof oracledb?.initOracleClient === 'function') {
         oracledb.initOracleClient({ libDir: instantClientLibDir });
         this.logger.info('(OracleService) Oracle Client Thick mode initialized successfully.');
      } else {
          this.logger.error('(OracleService) oracledb.initOracleClient is not available. Thick mode requires the oracledb driver and Instant Client.');
          throw new Error('oracledb thick mode initialization failed.');
      }


      // 手动配置 Oracle DataSource
      // *** 把你的 Oracle 连接参数放在这里 ***
      const oracleOptions: DataSourceOptions = {
          type: 'oracle',
          host: '218.59.245.145', // 请确认
          port: 51521,           // 请确认
          username: 'system',      // 请确认
          password: '1234',       // 请确认密码
          sid: 'ORCL',           // 请确认 SID 或改用 serviceName/connectString
          // logging: ['error', 'warn'], // 根据需要添加日志
          // entities: [], // 通常手动管理的不需要指定实体
          // 其他 Oracle 特定选项...
      };

      this.oracleDataSource = new DataSource(oracleOptions);
      await this.oracleDataSource.initialize();
      this.logger.info('(OracleService) Manual Oracle DataSource initialized successfully.');
      this.isInitialized = true;

    } catch (err) {
      this.logger.error('(OracleService) Failed to initialize Oracle Client or DataSource:', err);
      this.oracleDataSource = null; // 初始化失败则设为 null
      this.isInitialized = false; // 标记为未初始化
    }
  }

  /**
   * 获取手动创建的 Oracle DataSource 实例
   * @returns DataSource | null 返回 DataSource 实例，如果初始化失败则返回 null
   */
  getDataSource(): DataSource | null {
    if (!this.isInitialized || !this.oracleDataSource) {
         this.logger.warn('(OracleService) Oracle DataSource accessed before successful initialization or initialization failed.');
    }
    return this.oracleDataSource;
  }

  /**
   * 获取 Oracle QueryRunner (如果需要)
   * 注意: 使用完 QueryRunner 后需要手动释放 (queryRunner.release())
   * @returns Promise<QueryRunner | null>
   */
  async getQueryRunner() {
      const ds = this.getDataSource();
      if(ds && ds.isInitialized) {
          const queryRunner = ds.createQueryRunner();
          await queryRunner.connect(); // 确保连接
          return queryRunner;
      }
      this.logger.error('(OracleService) Cannot get QueryRunner because DataSource is not available/initialized.');
      return null;
  }

  // 可选: 添加一个 onStop 方法来关闭连接
  async onStop() {
      if(this.oracleDataSource && this.oracleDataSource.isInitialized) {
          await this.oracleDataSource.destroy();
          this.logger.info('(OracleService) Manual Oracle DataSource destroyed.');
      }
  }
} 